﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace VkSample113;

public class SkyBallData
{
    public float[] Data { get; set; }
    public int DataBytes { get; set; }
    public int VCount { get; set; }

    public void GenVertexData()
    {
        float radius = Constant.Sky_R;
        float ANGLE_SPAN = 18;//切分间隔
        float angleV = 90;//纵向上的起始度数
		List<float> texCoorArray = GenerateSkyTexCoor
			((int)(360 / ANGLE_SPAN), //纹理图切分的列数
			(int)(angleV / ANGLE_SPAN));  //纹理图切分的行数
		int tc = 0;//纹理数组计数器
		int ts = texCoorArray.Count;
		List<float> alVertix = new List<float>();
		List<float> alTexCoor = new List<float>();
		for (float vAngle = angleV; vAngle > 0; vAngle = vAngle - ANGLE_SPAN)//垂直方向angleSpan度一份
        {
			for (float hAngle = 360; hAngle > 0; hAngle = hAngle - ANGLE_SPAN)//水平方向angleSpan度一份
            {
				//纵向横向各到一个角度后计算对应的此点在球面上的四边形顶点坐标
				//并构建两个组成四边形的三角形
				double xozLength = radius * MathF.Cos(toRadians(vAngle));
				float x1 = (float)(xozLength * MathF.Cos(toRadians(hAngle)));
				float z1 = (float)(xozLength * MathF.Sin(toRadians(hAngle)));
				float y1 = (float)(radius * MathF.Sin(toRadians(vAngle)));

				xozLength = radius * MathF.Cos(toRadians(vAngle - ANGLE_SPAN));
				float x2 = (float)(xozLength * MathF.Cos(toRadians(hAngle)));
				float z2 = (float)(xozLength * MathF.Sin(toRadians(hAngle)));
				float y2 = (float)(radius * MathF.Sin(toRadians(vAngle - ANGLE_SPAN)));

				xozLength = radius * MathF.Cos(toRadians(vAngle - ANGLE_SPAN));
				float x3 = (float)(xozLength * MathF.Cos(toRadians(hAngle - ANGLE_SPAN)));
				float z3 = (float)(xozLength * MathF.Sin(toRadians(hAngle - ANGLE_SPAN)));
				float y3 = (float)(radius * MathF.Sin(toRadians(vAngle - ANGLE_SPAN)));

				xozLength = radius * MathF.Cos(toRadians(vAngle));
				float x4 = (float)(xozLength * MathF.Cos(toRadians(hAngle - ANGLE_SPAN)));
				float z4 = (float)(xozLength * MathF.Sin(toRadians(hAngle - ANGLE_SPAN)));
				float y4 = (float)(radius * MathF.Sin(toRadians(vAngle)));

				//构建第一三角形
				alVertix.Add(x1); alVertix.Add(y1); alVertix.Add(z1);
				alVertix.Add(x4); alVertix.Add(y4); alVertix.Add(z4);
				alVertix.Add(x2); alVertix.Add(y2); alVertix.Add(z2);

				//构建第二三角形

				alVertix.Add(x2); alVertix.Add(y2); alVertix.Add(z2);
				alVertix.Add(x4); alVertix.Add(y4); alVertix.Add(z4);
				alVertix.Add(x3); alVertix.Add(y3); alVertix.Add(z3);

				//第一三角形3个顶点的6个纹理坐标
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				//第二三角形3个顶点的6个纹理坐标
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
				alTexCoor.Add(texCoorArray[tc++ % ts]);
			}
		}
		VCount = alVertix.Count / 3;
		DataBytes = VCount * 5 * sizeof(float);
		Data = new float[VCount * 5];
		int index = 0;
		for (int i = 0; i < VCount; i++)
		{
			Data[index++] = alVertix[i * 3 + 0];
			Data[index++] = alVertix[i * 3 + 1];
			Data[index++] = alVertix[i * 3 + 2];
			Data[index++] = alTexCoor[i * 2 + 0];
			Data[index++] = alTexCoor[i * 2 + 1];
		}
	}

	float toRadians(float degree)
	{//角度转换成弧度的方法
		return (float)degree * MathF.PI / 180;
	}
	float toDegrees(float radian)
	{//弧度变换成角度的方法
		return (float)radian * 180 / MathF.PI;
	}
	private List<float> GenerateSkyTexCoor(int bw, int bh)
    {
        List<float> result = new List<float>();
        float sizew = 1.0f / bw;//列数
        float sizeh = 1.0f / bh;//行数
		for (int i = 0; i < bh; i++)
		{
			for (int j = 0; j < bw; j++)
			{
				//每行列一个矩形，由两个三角形构成，共六个点，12个纹理坐标
				float s = j * sizew;
				float t = i * sizeh;

				result.Add(s);
				result.Add(t);

				result.Add(s + sizew);
				result.Add(t);

				result.Add(s);
				result.Add(t + sizeh);

				result.Add(s);
				result.Add(t + sizeh);

				result.Add(s + sizew);
				result.Add(t);

				result.Add(s + sizew);
				result.Add(t + sizeh);
			}
		}
		return result;
	}
}
